package cn.micro.keep.accounts.config;

import cn.micro.keep.accounts.auth.JwtAuthenticationFilter;
import cn.micro.keep.accounts.auth.JwtTokenManager;
import cn.micro.keep.accounts.auth.exception.MyAuthenticationEntryPoint;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.config.http.SessionCreationPolicy;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter;

@Configuration
@EnableWebSecurity
@EnableGlobalMethodSecurity(
        prePostEnabled = true,
        securedEnabled = true,
        jsr250Enabled = true)
public class SecurityConfig extends WebSecurityConfigurerAdapter {

    final MyAuthenticationEntryPoint jwtAuthenticationEntryPoint;

    final IgnoreUrlsConfig ignoreUrlsConfig;

    final JwtTokenManager jwtTokenManager;

    public SecurityConfig(MyAuthenticationEntryPoint jwtAuthenticationEntryPoint, IgnoreUrlsConfig ignoreUrlsConfig, JwtTokenManager jwtTokenManager) {
        this.jwtAuthenticationEntryPoint = jwtAuthenticationEntryPoint;
        this.ignoreUrlsConfig = ignoreUrlsConfig;
        this.jwtTokenManager = jwtTokenManager;
    }


    @Bean
    public JwtAuthenticationFilter jwtRequestFilter(){
        return new JwtAuthenticationFilter(jwtTokenManager, ignoreUrlsConfig);
    }

    @Bean
    public PasswordEncoder passwordEncoder(){
        return new BCryptPasswordEncoder();
    }

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        // We don't need CSRF for this example
        http.cors().and().csrf().disable()
                // dont authenticate this particular request
                .authorizeRequests().antMatchers(ignoreUrlsConfig.getUrls().toArray(new String[0])).permitAll().
                // all other requests need to be authenticated
                        anyRequest().authenticated()
//                .and().logout().logoutUrl("/auth/logout").addLogoutHandler(chargeDoctorLogoutHandler).logoutSuccessHandler(chargeDoctorLogoutSuccessHandler).invalidateHttpSession(true).deleteCookies()
                // make sure we use stateless session; session won't be used to
                // store user's state.
                .and().exceptionHandling().authenticationEntryPoint(jwtAuthenticationEntryPoint).and().sessionManagement()
                // 基于token，所以不需要session
                .sessionCreationPolicy(SessionCreationPolicy.STATELESS)
                ;


        // 验证码校验过滤器
//        http.addFilterBefore(verifyCodeFilter,UsernamePasswordAuthenticationFilter.class);
        // Add a filter to validate the tokens with every request
        http.addFilterBefore(jwtRequestFilter(), UsernamePasswordAuthenticationFilter.class);


    }
}
